package com.example.register.service;

import com.example.register.mapper.UserAuthCodeMapper;
import com.example.register.mapper.UserMapper;
import com.example.register.mapper.UserInfoMapper;
import com.example.register.entity.Result;
import com.example.register.entity.User;
import com.example.register.entity.UserAuthCode;
import com.example.register.entity.UserInfo;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Base64;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

//实现
@Service
public class UserServiceImp implements UserService{

    @Autowired
    private UserMapper userMapper; //可以直接调用UserDao的所有方法
    @Autowired
    private UserInfoMapper userInfoMapper;
    @Autowired
    private UserAuthCodeMapper userAuthCodeMapper;


    @Override
    public User findUserByUsername(String mobile){
        return userMapper.findUserByUsername(mobile);
    }

    @Override
    public int insertUserInfo(UserInfo userInfo) {
        return userInfoMapper.insertUserInfo(userInfo);
    }
    @Override
    public int insertUserAuthCode(UserAuthCode userAuthCode) {
        return userAuthCodeMapper.insertUserAuthCode(userAuthCode);
    }
    @Override
    public int insertUser(User user) {
        return userMapper.insertUser(user);
    }


    //验证密码是否满足要求
    public  boolean isPasswdRight(String str) {
        boolean isDigit = false;//定义一个boolean值，用来表示是否包含数字
        boolean isLetter = false;//定义一个boolean值，用来表示是否包含字母
        boolean isSpecial = false;//定义一个boolean值，用来表示是否包含特殊字符

        for (int i = 0; i < str.length(); i++) {
            //判断是否含有特殊字符
            Pattern p = Pattern.compile("[~`#$%^&*!@.,()\\\\{}|:;?<>]");
            Matcher m = p.matcher(str);
            if (Character.isDigit(str.charAt(i))) {   //用char包装类中的判断数字的方法判断每一个字符
                isDigit = true;
            } else if (Character.isLetter(str.charAt(i))) {  //用char包装类中的判断字母的方法判断每一个字符
                isLetter = true;
            }else if (m.find()) {//判断是否包含特殊字符
                isSpecial = true;
            }
        }
        //密码的正则规则 8到12位  包含数字 字母 特殊字符!@.,()
        String regex = "^([a-zA-Z0-9~`#$%^&*!@.,()\\\\{}|:;?<>]){8,12}$";
        boolean isRight = isDigit && isLetter && isSpecial && str.matches(regex);
        return isRight;
    }
    //使用md5加密
    private static String md5(String password) {
        try {
            MessageDigest md = MessageDigest.getInstance("md5");
            byte[] bytes = md.digest(password.getBytes());
            String str = Base64.getEncoder().encodeToString(bytes);
            return str;
        } catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
        }
        return null;
    }

    //生成user
    public User getUser(Map<String, String> regInfo){
        User user = new User();
        user.setMobile(regInfo.get("mobile"));
        String password = regInfo.get("password");
        user.setPassword(md5(md5(password)));
        return user;
    }

    //生成userInfo
    public UserInfo getUserInfo(Map<String, String> regInfo){
        UserInfo userInfo = new UserInfo();
        userInfo.setNumber(regInfo.get("number"));
        userInfo.setName(regInfo.get("name"));
        userInfo.setGender(String.valueOf(regInfo.get("gender")));
        userInfo.setEmail(regInfo.get("email"));
        return userInfo;
    }

    //生成userAuthCode
    public UserAuthCode getUserAuthCode(Map<String, String> regInfo){
        UserAuthCode userAuthCode = new UserAuthCode();
        //生成认证码
        String authCode = String.valueOf((int)(Math.random()*900000 + 100000));
        userAuthCode.setCode(authCode);
        return userAuthCode;
    }

    //注册，新增一个用户
    public Result register(Map<String,String> regInfo){
        Result result = new Result();
        final String REGEX_STUDENTID = "\\d{10}$";
        final String REGEX_GENDER = "[0-1]$";
        final String REGEX_EMAIL = "^\\s*\\w+(?:\\.{0,1}[\\w-]+)*@[a-zA-Z0-9]+(?:[-.][a-zA-Z0-9]+)*\\.[a-zA-Z]+\\s*$";
        //判断手机号是否满足要求
        final String REGEX_MOBILE = "^[1][3,4,5,7,8][0-9]{9}$";
        //对数据进行一些判断
        if (!Pattern.matches(REGEX_STUDENTID,regInfo.get("number"))){
            result.setStatus(400);
            result.setMsg("学号格式不正确");
            return result;
        }else if (!Pattern.matches(REGEX_GENDER, String.valueOf(regInfo.get("gender")))){
            result.setStatus(400);
            result.setMsg("性别错误");
            return result;
        }else if (!Pattern.matches(REGEX_EMAIL,  regInfo.get("email"))){
            result.setStatus(400);
            result.setMsg("邮箱格式错误");
            return result;
        }else if(!Pattern.matches(REGEX_MOBILE, regInfo.get("mobile"))){
            result.setStatus(400);
            result.setMsg("手机号格式错误");
            return result;
        }else if(!isPasswdRight(regInfo.get("password"))){
            //密码不符合要求
            result.setStatus(400);
            result.setMsg("注册失败，密码不符合要求，需长度8-12位，同时包括字母、数字、特殊符号");
            return result;
        }
        //检查是否注册过了，
//        User existUser = findUserByUsername(regInfo.get("mobile"));
//        if(existUser == null){}
//        else{
//            System.out.println(existUser.toString());
//            System.out.println(existUser.getId());
//            //手机号已经注册过
//            result.setStatus(400);
//            result.setMsg("注册失败，该手机号用户已经存在");
//            return result;
//        }

        UserInfo userInfo = getUserInfo(regInfo);
        UserAuthCode userAuthCode = getUserAuthCode(regInfo);
        User user = getUser(regInfo);
        //插入数据库
        try{
            insertUserInfo(userInfo);
            int uid = userInfo.getId();
            userAuthCode.setUid(uid);
            user.setUid(uid);
            insertUser(user);
            insertUserAuthCode(userAuthCode);
            result.setStatus(1);
            result.setMsg("注册成功");
        }catch (Exception e){
            System.out.println(e);
            result.setStatus(500);
            result.setMsg("注册失败");
        }

        return result;
    }


}

